package com.joint.web.action.mp;

import com.fz.us.base.bean.BaseEnum;
import com.fz.us.base.bean.Pager;
import com.fz.us.base.util.LogUtil;
import com.fz.us.base.util.mapper.BeanMapper;
import com.fz.us.dict.bean.DictBean;
import com.fz.us.dict.entity.Dict;
import com.fz.us.dict.service.DictService;
import com.google.common.collect.Lists;
import com.google.common.collect.Maps;
import com.google.common.collect.Sets;
import com.joint.base.bean.EnumManage;
import com.joint.base.bean.SystemConfig;
import com.joint.base.entity.Company;
import com.joint.base.entity.FileManage;
import com.joint.base.entity.Users;
import com.joint.base.entity.system.Locations;
import com.joint.base.mp.WxEchoMpServiceImpl;
import com.joint.base.mp.WxMpInCacheConfigStorage;
import com.joint.base.service.UsersService;
import com.joint.base.util.DataUtil;
import com.joint.base.util.StringUtils;
import com.joint.core.entity.ProBack;
import com.joint.core.entity.ProInfo;
import com.joint.core.service.ProBackService;
import com.joint.core.service.ProInfoService;
import com.joint.web.action.BaseController;
import fz.me.chanjar.weixin.common.bean.WxJsapiSignature;
import fz.me.chanjar.weixin.common.exception.WxErrorException;
import net.sf.json.JSONObject;
import org.apache.http.client.utils.DateUtils;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.ResponseBody;

import javax.annotation.Resource;
import java.io.IOException;
import java.io.InputStream;
import java.math.BigDecimal;
import java.net.HttpURLConnection;
import java.net.URL;
import java.util.*;

/**
 * 后台Action类 - 微信首页
 * ============================================================================
 * 版权所有 2014 min_xu。
 * ----------------------------------------------------------------------------
 *
 * @author min_xu
 *
 * @version 1.1 2014-3-31
 */

@Controller
@RequestMapping(value = "/mp")
public class AjaxProbackController extends BaseController {
    private static final long serialVersionUID = -5383463207248344967L;

    @Resource
    private ProBackService proBackService;
    @Resource
    private ProInfoService proInfoService;
    @Resource
    private DictService dictService;
    @Resource
    private UsersService usersService;
    @Resource
    private WxEchoMpServiceImpl wxMpService;
    @Resource
    private WxMpInCacheConfigStorage wxMpInCacheConfigStorage;
    @Resource
    private SystemConfig systemConfig;


    //项目类别	选数据字典
    protected ArrayList<Map<String,Object>> typesArrayList;
    protected ArrayList<Map<String,List<Map<String,Object>>>> userArrayList;
    private  Map<String,List<Map<String,Object>>> userListMap;
    //人员选择列表
    protected List<Users> usersList;
    //反馈列表
    private List<ProBack> proBackList;

    private Set<Users> notice;

    private String keyId;
    private String dictId;
    private String proInfoId;
    private String proInfoName;
    private ArrayList<String> noticeId;

    private String backDate;
    private String content;
    private String mark;
    private int regular;
    private String latitude;
    private String longitude;

    private ProBack proBack;
    private ProInfo proInfo;
    private WxJsapiSignature jsapiSignature;
    private Set<String> imgUrl;
    /**
     * 微信服务器返回的MediaIds
     */
    private String wxMediaIds;

    private String error;
    private int hasImgs;


    //反馈地址
    private String address;

    @RequestMapping(value = "/ajax-proback/list", method = RequestMethod.POST)
    @ResponseBody
    public Map<String,Object> list(int page,String pageKeyword){
        List<JSONObject> dataRows = new ArrayList<JSONObject>();
        Map<String, Object> data = new HashMap<String, Object>();
        Map<String, Object> map = Maps.newHashMap();
        Map<String,Object> rmap;
        map.put("state", new BaseEnum.StateEnum[]{BaseEnum.StateEnum.Enable});
        Pager pager = new Pager();
        pager.setPageSize(10);
        pager.setPageNumber(page);
        pager.setOrderBy("createDate");
        pager.setOrderType(BaseEnum.OrderType.desc);
        pager.setPageNumber(page);
        if(StringUtils.isNotEmpty(pageKeyword)){
            map.put("name", pageKeyword);
            pager.setKeyword(pageKeyword);
        }
        Company com = usersService.getCompanyByUser();
        Users users=usersService.getLoginInfo();
        if (StringUtils.isNotEmpty(pageKeyword)){
            map.put("proInfo.name",pageKeyword);
            pager = proBackService.findByPagerAndCompany(pager, null, com, map);
        }
        if (StringUtils.isNotEmpty(proInfoId)) {
            proInfo = proInfoService.get(proInfoId);
            pager = proBackService.findByPagerAndProInfo(pager, proInfo, new BaseEnum.StateEnum[]{BaseEnum.StateEnum.Enable});
        }
        if(StringUtils.isEmpty(pageKeyword) && StringUtils.isEmpty(proInfoId)){
            proBackService.findByPagerAndLimit(pager,users,com,map);
        }
        proBackList= (List<ProBack>) (proBackService.getTotalCount()>0?pager.getList():Lists.newArrayList());
        for(ProBack proBack:proBackList){
            rmap=Maps.newHashMap();
            rmap.put("id",proBack.getId());
            rmap.put("name",proBack.getName());
            rmap.put("backDate", DateUtils.formatDate(proBack.getBackDate(),"yyyy-MM-dd"));
            rmap.put("url",getPath()+"mp/ajax-proback/read/"+proBack.getId());
            rmap.put("content",proBack.getContent());
            rmap.put("proInfo",proBack.getProInfo().getName());
            rmap.put("category",proBack.getCategory().getName());
            rmap.put("creater",proBack.getCreater().getName());
            rmap.put("regular",proBack.getRegular()==1?"正常":"不正常");
            dataRows.add(JSONObject.fromObject(rmap));
        }
        data.put("pageNum", pager.getPageNumber());//页数
        data.put("pageSize", dataRows.size());//记录数
        data.put("pageCount", pager.getPageCount());//总页数
        data.put("totalCount", pager.getTotalCount());//总记录数
        data.put("pageKeyword", pager.getKeyword()==null?"": pager.getKeyword());//查询
        data.put("dataRows", dataRows);//数据
        return ajaxHtmlAppResult(1, "", JSONObject.fromObject(data));
    }
    public String allList(){
        pager = new Pager();
        rows = LISTVIEW_WEB_SIZE;
        pager.setPageSize(rows);
        pager.setPageNumber(page);
        pager.setOrderBy("createDate");
        pager.setOrderType(BaseEnum.OrderType.desc);

        Company com = usersService.getCompanyByUser();
        Users users=usersService.getLoginInfo();
        Map<String,Object> params = new HashMap<String,Object>();
        params.put("state", BaseEnum.StateEnum.Enable);

        pager = proBackService.findByPagerAndLimit(pager,users,com,params);
        proBackList= (List<ProBack>) (pager.getTotalCount()>0?pager.getList():Lists.newArrayList());
        //pager=proBackService.findByPagerAndCompany(pager,null,com,params);

        return "allList";
    }

    public String listByPro(){
        pager = new Pager();
        rows = LISTVIEW_WEB_SIZE;
        pager.setPageSize(rows);
        pager.setPageNumber(page);
        pager.setOrderBy("createDate");
        pager.setOrderType(BaseEnum.OrderType.desc);

        Company com = usersService.getCompanyByUser();
        Users users=usersService.getLoginInfo();
        Map<String,Object> params = new HashMap<String,Object>();
        params.put("state", BaseEnum.StateEnum.Enable);

        pager = proBackService.findByPagerAndLimit(pager, users, com, params);
       // pager=proBackService.findByPagerAndCompany(pager,null,com,params);
        proBackList= (List<ProBack>) (pager.getTotalCount()>0?pager.getList():Lists.newArrayList());
        return "list";
    }

    public String view(){
        return "view";
    }

    public String tabview(){
        return "tabview";
    }

    public String isCreater(String id){
        Users users=usersService.getLoginInfo();
        Company com=usersService.getCompanyByUser();
        if(StringUtils.isEmpty(id)){
            return ajaxHtmlCallback("400","请先选择项目","操作提示");
        }
        proBack =proBackService.get(id);
        //只有成员和新建者可编辑
        if(StringUtils.equals(proBack.getCreater().getId(), users.getId()) && proBack.getProInfo().getGroup().contains(users)){
            return "block";
        }else{
            return "";
        }
    }
    @RequestMapping(value = "/ajax-proback/read/{keyId}", method = RequestMethod.GET)
    public String read(Model model,@PathVariable("keyId") String keyId){
        LogUtil.info("keyId:" + keyId);
        if(StringUtils.isNotEmpty(keyId)){
            proBack = proBackService.get(keyId);
            if(StringUtils.isNotEmpty(proBack.getLocationId())){
                Locations locations= locationsService.get(proBack.getLocationId());
                address=locationsService.getAddress(locations);
            }else{
                address="";
            }
            Set<FileManage> urls = proBack.getPicsUrl();

            if(null != urls){
                String base = wxMpInCacheConfigStorage.getHttpHost() + "/" + systemConfig.getWebroot();
                //imgUrl
                imgUrl = Sets.newHashSet();
                for (FileManage fileManage : urls){
                    imgUrl.add(base + "/mp/file.action?gridId="+fileManage.getGridId());
                }
            }

        }
        LogUtil.info("imgUrl:" + imgUrl);
        //增加照片阅览功能
        //String url = wxMpInCacheConfigStorage.getHttpHost() + "/" + systemConfig.getWebroot() + "/mp/ajax-proback!read.action?keyId=" + keyId;
        String url = getRequest().getRequestURL() + "?keyId=" + keyId;
        //LogUtil.info("{ url }"+url);
        try {
            jsapiSignature =  wxMpService.createJsapiSignature(url);
            jsapiSignature.setAppId(wxMpInCacheConfigStorage.getAppId());
            model.addAttribute("jsapiSignature", jsapiSignature);
            model.addAttribute("address",address);
            model.addAttribute("imgUrl",imgUrl);
            model.addAttribute("proBack",proBack);
        } catch (WxErrorException e) {
            LogUtil.info(e);
        }
        return "/mp/ajax-proback_read";
    }

    public String input(){
        //LogUtil.info("request url:" + getRequest().getRequestURL());
        if (StringUtils.isNotEmpty(proInfoId)){
            proInfo = proInfoService.get(proInfoId);
            proInfoId = proInfo.getId();
            proInfoName = proInfo.getName();

            //如果不是该项目的总监或项目组成员，则不允许新建
            Users users = usersService.getLoginInfo();
            int flg = 0;
            if (users.equals(proInfo.getChief())){
                flg = 1;
            }else{
                Set<Users> usersSet = proInfo.getGroup();
                if(usersSet.size()>0){
                    if(usersSet.contains(users)){
                         flg = 1;
                    }
                }
            }
            if(flg==0){
                error = "您不是该项目的总监或项目组成员，不允许新建！";
                return "error";
                //return ajaxHtmlCallback("404", "您不是该项目的总监或项目组成员，不允许新建！","操作状态");
            }
        }


        if (StringUtils.isNotEmpty(keyId)){
            proBack = proBackService.get(keyId);

        }else{
            proBack = new ProBack();
            if (StringUtils.isNotEmpty(proInfoId)){
                proBack.setProInfo(proInfo);
            }
        }

        Company company = usersService.getCompanyByUser();

        Map<String,Object> rMap = null;
        typesArrayList = new ArrayList<Map<String, Object>>();
        for(Dict typeObj:dictService.listFormDefinedEnable(DictBean.DictEnum.ProBackCategory, company.getId())){
            rMap = new HashMap<String, Object>();
            rMap.put("id",typeObj.getId());
            rMap.put("name", typeObj.getName());
            if(StringUtils.isNotEmpty(keyId) && proBack !=null && proBack.getCategory().equals(typeObj)){
                rMap.put("selected","selected");
            }else {
                rMap.put("selected","");
            }
            typesArrayList.add(rMap);
        }
        Pager upager = new Pager(0);
        upager.setOrderBy("pinYinHead");
        upager.setOrderType(BaseEnum.OrderType.asc);

        usersList = (List<Users>) usersService.findByPagerAndCompany(upager, null, company, new BaseEnum.StateEnum[]{BaseEnum.StateEnum.Enable}).getList();

        userListMap = Maps.newLinkedHashMap();
        for(Users users : usersList){
            List<Map<String,Object>> tmplist = null;
            String pinyinHead = users.getPinYinHead();
            String headstr = "";
            if(pinyinHead != null){
                headstr = StringUtils.upperCase(String.valueOf(pinyinHead.charAt(0)));
            }
            if(userListMap.containsKey(headstr)){
                tmplist = userListMap.get(headstr);
                tmplist.add(packageMap(users,proBack));
            }else {
                tmplist = Lists.newArrayList();
                tmplist.add(packageMap(users, proBack));
            }
            userListMap.put(headstr, tmplist);
        }

        //增加已上传照片列表显示
        hasImgs = 0;
        if(StringUtils.isNotEmpty(keyId)){

            Set<FileManage> urls = proBack.getPicsUrl();

            if(null != urls && urls.size()>0){
                String base = wxMpInCacheConfigStorage.getHttpHost() + "/" + systemConfig.getWebroot();
                //imgUrl
                imgUrl = Sets.newHashSet();
                for (FileManage fileManage : urls){
                    imgUrl.add(base + "/mp/file.action?gridId="+fileManage.getGridId());
                }
                hasImgs = 1;
            }
        }
        LogUtil.info("{ hasImgs }"+hasImgs);
        //反馈增加拍照和上传照片功能
        //String url = wxMpInCacheConfigStorage.getHttpHost() + "/" + systemConfig.getWebroot() + "/mp/ajax-proback!input.action?proInfoId=" + proInfoId;
        String url;
        if (StringUtils.isNotEmpty(keyId)){
            url = getRequest().getRequestURL() + "?keyId=" + keyId;
        }else{
            url = getRequest().getRequestURL() + "?proInfoId=" + proInfoId;
        }
        //String url = getRequest().getRequestURL() + "?proInfoId=" + proInfoId;
        LogUtil.info("{ url }"+url);
        try {
            jsapiSignature =  wxMpService.createJsapiSignature(url);
            jsapiSignature.setAppId(wxMpInCacheConfigStorage.getAppId());
            //LogUtil.info("appId:" + jsapiSignature.getAppId() );
        } catch (WxErrorException e) {
            LogUtil.info(e);
        }

        return  "input";
    }


    public String save() throws WxErrorException {
        //LogUtil.info("keyId:"+keyId);
        ProBack preBack = null;
        if(StringUtils.isNotEmpty(keyId)){
            proBack = proBackService.get(keyId);
            preBack = BeanMapper.map(proBack, ProBack.class);
        }else{
            proBack = new ProBack();
            proBack.setCreater(usersService.getLoginInfo());
        }

        if (StringUtils.isNotEmpty(dictId)){
            Dict dict = dictService.get(dictId);
            proBack.setCategory(dict);
        }
        if (StringUtils.isNotEmpty(proInfoId)){
            ProInfo proInfo = proInfoService.get(proInfoId);
            proBack.setProInfo(proInfo);
            proBack.setName(proInfo.getName());
        }
        if (StringUtils.isNotEmpty(backDate)){
            proBack.setBackDate(DataUtil.StringToDate(backDate, "yyyy-MM-dd"));
        }

        proBack.setContent(content);
        proBack.setMark(mark);
        proBack.setRegular(regular);
        if (noticeId!=null && noticeId.size()>0) {
            Set<Users> group = new HashSet<Users>();
            for(String userId : noticeId){
                if(StringUtils.isEmpty(userId)) continue;
                //LogUtil.info("userId:"+userId);
                Users user = usersService.get(userId);
                group.add(user);
            }
            proBack.setNotice(group);
        }

        //LogUtil.info("wxMediaIds:"+wxMediaIds);
        if (StringUtils.isNotEmpty(wxMediaIds)){
            Set<FileManage> picsUrl = Sets.newHashSet();
            if (StringUtils.isNotEmpty(keyId)){
                picsUrl = proBack.getPicsUrl();
            }

           // LogUtil.info("picsUrl size:"+picsUrl.size());

            FileManage fileManage;
            String[] mediaIds = wxMediaIds.split(",");
            for(String mediaId : mediaIds){
                //LogUtil.info("mediaId:"+mediaId);
                //从微信服务器上取回图片
                try {
                    fileManage = gridFSSave(getInputStream(mediaId), mediaId+".jpg", mediaId,"APPLICATION/OCTET-STREAM",ProBack.class);
                    picsUrl.add(fileManage);
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
            proBack.setWxMediaIds(wxMediaIds);
            proBack.setPicsUrl(picsUrl);
            proBack.setPicAmount(picsUrl.size());
        }

        proBack.setCompany(usersService.getCompanyByUser());

        Locations locations=new Locations();
        locations.setLatitude(new BigDecimal(latitude));
        locations.setLongitude(new BigDecimal(longitude));
        locations.setCoordType(EnumManage.CoordTypeEnum.wgs84);
        proBackService.updateAndResume(proBack,preBack,locations);
        return ajaxHtmlCallback("200", "保存成功！",proInfoId);
    }

    /**
     * 获得输入流
     * @param mediaId
     * @return
     */
    public InputStream getInputStream(String mediaId) {
        String t = wxMpInCacheConfigStorage.getTokenFromCache();

        InputStream is = null;

        String url = "http://file.api.weixin.qq.com/cgi-bin/media/get?access_token="
                + t + "&media_id=" + mediaId;

        try {
            URL urlGet = new URL(url);

            HttpURLConnection http = (HttpURLConnection) urlGet.openConnection();

            http.setRequestMethod("GET"); // 必须是get方式请求

            http.setRequestProperty("Content-Type","application/x-www-form-urlencoded");

            http.setDoOutput(true);

            http.setDoInput(true);

            System.setProperty("sun.net.client.defaultConnectTimeout", "30000");// 连接超时30秒

            System.setProperty("sun.net.client.defaultReadTimeout", "30000"); // 读取超时30秒

            http.connect();

            // 获取文件转化为byte流
            is = http.getInputStream();

        } catch (Exception e) {
            e.printStackTrace();
        }

        return is;
    }

    public String delete(){
        if(StringUtils.isEmpty(keyId)){
            return ajaxHtmlCallback("200", "请选择客户信息！","操作状态");
        }
        ProInfo proInfo = proInfoService.get(keyId);
        proInfo.setState(BaseEnum.StateEnum.Delete);
        proInfoService.update(proInfo);
        return ajaxHtmlCallback("200", "保存成功！","操作状态");
    }

    private Map<String,Object> packageMap(Users users,ProBack proBack){
        Map<String,Object> rMap = new HashMap<String, Object>();
        rMap.put("id",users.getId());
        rMap.put("name", users.getName());
        if(StringUtils.isNotEmpty(keyId) && proBack !=null && proBack.getNotice().contains(users)) {
            rMap.put("selected","selected");
        }else {
            rMap.put("selected","");
        }
        return rMap;
    }
    @Override
    public String getKeyId() {
        return keyId;
    }

    @Override
    public void setKeyId(String keyId) {
        this.keyId = keyId;
    }

    public String getProInfoId() {
        return proInfoId;
    }

    public void setProInfoId(String proInfoId) {
        this.proInfoId = proInfoId;
    }

    public ArrayList<Map<String, Object>> getTypesArrayList() {
        return typesArrayList;
    }

    public void setTypesArrayList(ArrayList<Map<String, Object>> typesArrayList) {
        this.typesArrayList = typesArrayList;
    }

    public String getDictId() {
        return dictId;
    }

    public void setDictId(String dictId) {
        this.dictId = dictId;
    }

    public Set<Users> getNotice() {
        return notice;
    }

    public void setNotice(Set<Users> notice) {
        this.notice = notice;
    }

    public String getContent() {
        return content;
    }

    public void setContent(String content) {
        this.content = content;
    }

    public String getMark() {
        return mark;
    }

    public void setMark(String mark) {
        this.mark = mark;
    }

    public int getRegular() {
        return regular;
    }

    public void setRegular(int regular) {
        this.regular = regular;
    }

    public ProBack getProBack() {
        return proBack;
    }

    public void setProBack(ProBack proBack) {
        this.proBack = proBack;
    }

    public String getBackDate() {
        return backDate;
    }

    public void setBackDate(String backDate) {
        this.backDate = backDate;
    }

    public ArrayList<String> getNoticeId() {
        return noticeId;
    }

    public void setNoticeId(ArrayList<String> noticeId) {
        this.noticeId = noticeId;
    }

    public String getProInfoName() {
        return proInfoName;
    }

    public void setProInfoName(String proInfoName) {
        this.proInfoName = proInfoName;
    }

    public ProInfo getProInfo() {
        return proInfo;
    }

    public void setProInfo(ProInfo proInfo) {
        this.proInfo = proInfo;
    }

    public List<Users> getUsersList() {
        return usersList;
    }

    public void setUsersList(List<Users> usersList) {
        this.usersList = usersList;
    }

    public ArrayList<Map<String, List<Map<String, Object>>>> getUserArrayList() {
        return userArrayList;
    }

    public void setUserArrayList(ArrayList<Map<String, List<Map<String, Object>>>> userArrayList) {
        this.userArrayList = userArrayList;
    }

    public List<ProBack> getProBackList() {
        return proBackList;
    }

    public void setProBackList(List<ProBack> proBackList) {
        this.proBackList = proBackList;
    }



    public WxJsapiSignature getJsapiSignature() {
        return jsapiSignature;
    }

    public void setJsapiSignature(WxJsapiSignature jsapiSignature) {
        this.jsapiSignature = jsapiSignature;
    }

    public Set<String> getImgUrl() {
        return imgUrl;
    }

    public void setImgUrl(Set<String> imgUrl) {
        this.imgUrl = imgUrl;
    }

    public String getWxMediaIds() {
        return wxMediaIds;
    }

    public void setWxMediaIds(String wxMediaIds) {
        this.wxMediaIds = wxMediaIds;
    }

    public String getError() {
        return error;
    }

    public void setError(String error) {
        this.error = error;
    }

    public int getHasImgs() {
        return hasImgs;
    }

    public void setHasImgs(int hasImgs) {
        this.hasImgs = hasImgs;
    }

    public Map<String, List<Map<String, Object>>> getUserListMap() {
        return userListMap;
    }

    public void setUserListMap(Map<String, List<Map<String, Object>>> userListMap) {
        this.userListMap = userListMap;
    }

    public String getLatitude() {
        return latitude;
    }

    public void setLatitude(String latitude) {
        this.latitude = latitude;
    }

    public String getLongitude() {
        return longitude;
    }

    public void setLongitude(String longitude) {
        this.longitude = longitude;
    }

    public String getAddress() {
        return address;
    }

    public void setAddress(String address) {
        this.address = address;
    }

}
